

package PDFd.Layer;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import android.graphics.Bitmap;
import android.graphics.Color;
import android.util.Log;
/**
* <p>Title: DrawingUtilities</p>
* <p>Description: A Utility class that can do generic actions on a layer. 
* This is more of a 'catch all' for functionalities that belong nowhere else. </p>
* @author Matt, Tom, Andrew, Kong
* @email matt.mckay@my.uwrf.edu,tom.florin@my.uwrf.edu,
* andrew.kathan@my.uwrf.edu,kong.xiong-1@my.uwrf.edu
* @date December 1st,2011*/
public class DrawingUtilities {
	/**
	 * A utility to average a bunch touch events over time.
	 * @author mckaym
	 */
	public static class TouchInputAverager {
		transient public List<Float> historyEvents;
		transient public Integer maximumHistory;
		public TouchInputAverager() {
			
		}
		/**
		 * Create a new instance of the 
		 * @param maximumHistory
		 */
		public TouchInputAverager(Integer maximumHistory) {
			this.maximumHistory = maximumHistory;
			reset();
		}
		public void reset() {
			historyEvents = new ArrayList<Float>();
		}
		
		/**
		 * A method to scale input based on pressure
		 * @param pressure
		 * @return total/historyEvents.size();
		 */
		public float scaleInput(float pressure) {
			historyEvents.add(pressure);
			if(historyEvents.size() == this.maximumHistory) {
				historyEvents.remove(0);
			}
			float total = 0;
			for(float f: historyEvents) {
				total += f;
			}
			return total/historyEvents.size();
		}
		
	}
	
	
	/**
	 * This method takes two points and pressure values, and returns 
	 * a map containing points between the provided values at 3 pixel
	 * increments
	 * @param p1 first point
	 * @param pressure1 first pressure
	 * @param p2 second point
	 * @param pressure2 second pressure
	 * @return Map<Point,Integer> points
	 */
	public static Map<Point,Integer> getPointsBetween(Point p1, int pressure1, Point p2, int pressure2){
		Map<Point, Integer> toReturn = new HashMap<Point,Integer>();
		//get the total distance between this and the last circle drawn
		double d = p2.distance(p1);
		if (d > 4){
		//divide by 3 to find 3 pixel increments within that distance
			d /= 3;
			double xIncrement = (p1.difference(p2).x/d);
			double yIncrement = (p1.difference(p2).y/d);
			//for every increment of 3 pixels of difference, draw a new circle there
			for(int i = 1; i < d; i++){
				toReturn.put(
					(new Point((int)(p1.x+xIncrement*i),(int)(p1.y+yIncrement*i))), 
					(int)(pressure1+(pressure2-pressure1)*i/d));
			}
		
		}
		toReturn.put(p1, pressure1);
		toReturn.put(p2, pressure2);
		return toReturn;
	}
	
	/**
	 * Returns a bitmap that is a 'dashed border' for the given layer Note, the
	 * contents of the layer are NOT included in this. The Bitmap returned is
	 * the exact size of the layer, meaning the edges of the layer may be
	 * overwritten
	 * 
	 * @param l
	 * @return
	 */
	public static Bitmap drawOutline(Layer l) {

		int canvasX = l.getCanvasSize().x;
		int canvasY = l.getCanvasSize().y;
		Log.i("DrawOutline", l.getCanvasSize().toString());
		Bitmap b = null;
		if (canvasX > 0 && canvasY > 0) {
			b = Bitmap.createBitmap(canvasX, canvasY, Bitmap.Config.ARGB_8888);
			for (int i = 0; i < canvasY - 1; i++) {
				b.setPixel(0, i, Color.BLACK);
				b.setPixel(canvasX - 1, i, Color.BLACK);
			}
			for (int i = 0; i < canvasX - 1; i++) {
				b.setPixel(i, 0, Color.BLACK);
				b.setPixel(i, canvasY - 1, Color.BLACK);
			}
		}
		return b;
	}
}
